package com.spukmk3me.animatorpack.pack0;

/* $if SPUKMK3ME_DEBUG$ */
import com.spukmk3me.debug.Logger;
/* $endif$ */
import com.spukmk3me.math.FPMath;
import com.spukmk3me.scene.Animator;
import com.spukmk3me.scene.Node;

public class ColorAnimator extends Animator
{
    public void setupColorAnimation( int startColor, int endColor, int deltaTime, byte manipulationType )
    {
        /* $if SPUKMK3ME_DEBUG$ */
        if ( deltaTime < 0 )
            Logger.trace( "deltaTime for ColorAnimator is negative: " + deltaTime );
        /* $endif$ */
        
        m_startColor        = startColor;
        m_endColor          = endColor;
        m_timeLeft          = Math.max( 0, deltaTime );
        m_manipulationType  = manipulationType;
        
        m_currentA = (m_startColor >> 8) & 0x00FF0000;
        m_currentR = m_startColor & 0x00FF0000;
        m_currentG = (m_startColor << 8) & 0x00FF0000;
        m_currentB = (m_startColor << 16) & 0x00FF0000;
        
        if ( m_timeLeft > 0 )
        {
            m_spdA = FPMath.fpDiv( ((endColor >> 8) & 0x00FF0000) - m_currentA, m_timeLeft );
            m_spdR = FPMath.fpDiv( (endColor & 0x00FF0000) - m_currentR, m_timeLeft );
            m_spdG = FPMath.fpDiv( ((endColor << 8) & 0x00FF0000) - m_currentG, m_timeLeft );
            m_spdB = FPMath.fpDiv( ((endColor << 16) & 0x00FF0000) - m_currentB, m_timeLeft );
        }
        
        if ( getNode() != null )
        {
            if ( manipulationType == TYPE_PLANECOLOR )
                getNode().setPlaneColor( startColor );
            else if ( manipulationType == TYPE_ADDITIONALCOLOR )
                getNode().setAdditionalColor( startColor );
        }
        
        m_initialized = true;
    }
    

    @Override
    protected void animate( int deltaTime )
    {
        if ( !m_initialized )
            return;
        
        if ( m_timeLeft > 0 )
        {
            int color =
                (FPMath.fpRound( m_currentA ) << 24) |
                (FPMath.fpRound( m_currentR ) << 16) |
                (FPMath.fpRound( m_currentG ) << 8) |
                FPMath.fpRound( m_currentB );
            
            if ( m_manipulationType == TYPE_PLANECOLOR )
                getNode().setPlaneColor( color );
            else if ( m_manipulationType == TYPE_ADDITIONALCOLOR )
                getNode().setAdditionalColor( color );
            
            m_currentA += FPMath.fpMul( m_spdA, deltaTime );
            m_currentR += FPMath.fpMul( m_spdR, deltaTime );
            m_currentG += FPMath.fpMul( m_spdG, deltaTime );
            m_currentB += FPMath.fpMul( m_spdB, deltaTime );
            
            m_timeLeft -= deltaTime;
        }
        
        if ( m_timeLeft <= 0 )
        {
            if ( m_manipulationType == TYPE_PLANECOLOR )
                getNode().setPlaneColor( m_endColor );
            else if ( m_manipulationType == TYPE_ADDITIONALCOLOR )
                getNode().setAdditionalColor( m_endColor );
        }
    }

    
    @Override
    public boolean isAnimating()
    {
        return m_timeLeft > 0;
    }
    
    @Override
    protected void onNodePrepareToChange( Node newNode ) {}
    
    @Override
    protected void onNodeChanged() {}

    public static final byte TYPE_PLANECOLOR        = 0;
    public static final byte TYPE_ADDITIONALCOLOR   = 1;
    
    private int m_startColor, m_endColor, m_timeLeft;
    private int m_spdA, m_spdR, m_spdG, m_spdB;
    private int m_currentA, m_currentR, m_currentG, m_currentB;
    private boolean m_initialized;
    private byte m_manipulationType;
}
